#include <jni.h>
#include <stdlib.h>
#include <memory.h>
#include <string.h>

#ifdef _WIN32
#define PATH_SEPARATOR ";"
#else
#define PATH_SEPARATOR ":"
#endif

JavaVM *jvm;				// a pointer to the JVM. We use this primarily to create, initialize, and destroy the JVM.
JNIEnv *env;				// represents JNI execution environment.
JavaVMInitArgs vm_args;		// represents various JVM arguments that we can use to initialize our JVM.
JavaVMOption options[1];	// holds various optional settings for the JVM.

char classpath[1000];
long status;

bool init(){ 
	const char *home = getenv("INHOME");
	if (!home) {
		printf("Failed to get INHOME.");
		return false;
	}

	// bug
	strcat(classpath, "-Djava.class.path=");
	strcat(classpath, home);
	strcat(classpath, "/indevcore2.jar");
	strcat(classpath, PATH_SEPARATOR);
	strcat(classpath, home);
	strcat(classpath, "/log4j-1.2.8.jar");
	printf("%s\n\n", classpath);
	options[0].optionString = classpath;	// set the classpath for the JVM, to enable it to find the required Java classes
	
	// Before we can use vm_args we need to set aside some memory for it:
	memset(&vm_args, 0, sizeof(vm_args));	// set aside enough memory for vm_args
	// Once we've set the memory, we can set the version and option arguments:
	vm_args.version = JNI_VERSION_1_6;		// version of Java platform
	vm_args.nOptions = 1;					// same as size of options[1]
	vm_args.options = options;

	return true;
}

int main(int argc, char *argv[])
{
	if (init()){
		
		// Ready to create a JVM.
		status = JNI_CreateJavaVM(&jvm, (void**)&env, &vm_args);

		if (status == JNI_OK)
		{
			// Once we've created our JVM, we're ready to begin running Java code in the native application.
			// First, we need to find and load our Java class, using the FindClass() function, shown here:
			jclass clazz = env->FindClass("in/util/TestEnv");
			if (clazz != 0)
			{
				const char *signature = "([Ljava/lang/String;)V";
				// jobject arg = env->NewStringUTF("-d");
				// jobjectArray argArray = env->NewObjectArray(1, env->FindClass("java/lang/String"), env->NewStringUTF(""));
				// env->SetObjectArrayElement(argArray, 0, arg);
				// Next, we want to find a method inside of the class using the GetStaticMethodID() function.
				jmethodID mid = env->GetStaticMethodID(clazz, "main", signature);	// if the method is found, the mid variable represents a handle to the method. If the method cannot be found, mid will be zero.
				if (mid != 0)
				{
					// Finally, we call the Java method
					env->CallStaticVoidMethod(clazz, mid);
					if (env->ExceptionOccurred())
					{
						env->ExceptionDescribe();
					}
				}
				else
				{
					printf("Failed to get method.");
					if (env->ExceptionOccurred())
					{
						env->ExceptionDescribe();
					}
				}

			}
			else
			{
				printf("Failed to get class.");	
				if (env->ExceptionOccurred())
				{
					env->ExceptionDescribe();
				}
			}

			jvm->DestroyJavaVM();
			return 0;
		}
		else
		{
			printf("Failed to create JVM.");
			if (env->ExceptionOccurred())
			{
				env->ExceptionDescribe();
			}
			return status;
		}
	}
	return -1;
}
